/*
 *  Copyright 2010 Wesley Gooch, Ryan Nix, Cody Wenzel.
 *  Montana State University - Spring Semester 2010
 *  Computer Science 450 - Compilers
 *  Project: Micro-Pascal Compiler
 */

import java.io.FileNotFoundException;
import java.io.FileReader;
import java.io.IOException;
import java.io.PushbackReader;
import java.util.logging.Level;
import java.util.logging.Logger;
import msu.compiler.parser.Parser;
import msu.compiler.scanner.Tokenizer;
import msu.compiler.scanner.Scanner;

/**
 * Compilier Entry Point. Pass the micro pascal file as the param to compile.
 * Example: <code>java mpCompile /path/to/program.mp</code>
 *
 * @author Wesley Gooch
 */
public class mpCompile {

    /**
     * Compiler point of entry.
     * 
     * @param args Full File System path to the micro-pascal file and/or options.
     */
    public static void main(String[] args) {

        System.out.print(HRULE + "-- Executing Compiler " + HRULE + "\n");

        if (args.length > 0) {
            // Arguments were supplied... decide what to do.
            String argument;
            for (int i = 0; i < args.length; i++) {
                argument = args[i];

                if (argument.equals("-h") || argument.equals("--help")) {
                    printHelpOptions();
                } else {
                    compile(argument);
                }
            }
        } else {
            System.out.print(
                    "Please pass in the full file system path \n"
                    + "to the Micro-Pascal file to be compile. \n");
            exit();
        }
    }

    /**
     * Wraps the instantiation of major components of the compiler and catches
     * the highest level of exceptions then exits. All other parser and scanner
     * errors should be handled in their own packages and not here.
     *
     * @param filePath  the full system path to the micro-pascal file.
     */
    private static void compile(String filePath) {
        Parser parser;
        Tokenizer tokenizer;
        Scanner scanner;

        try {

            // Attempt to read in the file & create tokenizer.
            PushbackReader inputReader = new PushbackReader(new FileReader(filePath), 100);
            tokenizer = new Tokenizer(inputReader);

            // Build the Scanner to give to the parser, then parse.
            scanner = new Scanner(tokenizer);
            parser = new Parser(scanner);
            parser.parse();

            try {
                inputReader.close();
            } catch (IOException ex) {
                Logger.getLogger(mpCompile.class.getName()).log(Level.SEVERE, null, ex);
            }

        } catch (FileNotFoundException ex) {

            Logger.getLogger(mpCompile.class.getName()).log(Level.SEVERE, null, ex);
            System.out.print("File Not Found. Try Again With A Different Path.");

        } catch (Exception e) {
            e.printStackTrace();
        } finally {
            exit();
        }
    }

    /**
     * Print out help instructions to the screen.
     */
    private static void printHelpOptions() {
        String help =
                "Micro-Pascal Compiler Help: \n\n"
                + "  -h       Displays this help screen. \n\n"
                + "  file     Pass a string containing the Micro-Pascal \n"
                + "           filename to be compiled. (Full Path)\n";
        System.out.print(help);
        exit();
    }

    /**
     * Cleanup loose ends, display log warnings, print out success or fail
     * message and exit program.
     */
    private static void exit() {
        System.out.print(HRULE + "-- Execution Complete " + HRULE);
        System.exit(0);
    }
    private final static String HRULE =
            "\n------------------------------------------------\n";
}
